```html
<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>零钱兑换算法可视化</title>
    <link href="https://cdn.staticfile.org/font-awesome/6.4.0/css/all.min.css" rel="stylesheet">
    <link href="https://cdn.staticfile.org/tailwindcss/2.2.19/tailwind.min.css" rel="stylesheet">
    <link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;500;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
    <script src="https://cdn.jsdelivr.net/npm/mermaid@latest/dist/mermaid.min.js"></script>
    <style>
        body {
            font-family: 'Noto Sans SC', Tahoma, Arial, Roboto, "Droid Sans", "Helvetica Neue", "Droid Sans Fallback", "Heiti SC", "Hiragino Sans GB", Simsun, sans-serif;
            background-color: #f8fafc;
            color: #1e293b;
        }
        .hero-gradient {
            background: linear-gradient(135deg, #3b82f6 0%, #6366f1 100%);
        }
        .code-block {
            background-color: #1e293b;
            border-radius: 0.5rem;
            overflow: hidden;
        }
        .dp-cell {
            transition: all 0.3s ease;
        }
        .dp-cell:hover {
            transform: scale(1.05);
            box-shadow: 0 10px 15px -3px rgba(0, 0, 0, 0.1), 0 4px 6px -2px rgba(0, 0, 0, 0.05);
        }
        .concept-card {
            transition: all 0.3s ease;
            border-left: 4px solid #3b82f6;
        }
        .concept-card:hover {
            transform: translateY(-5px);
            box-shadow: 0 10px 15px -3px rgba(0, 0, 0, 0.1), 0 4px 6px -2px rgba(0, 0, 0, 0.05);
        }
        .highlight {
            position: relative;
            z-index: 1;
        }
        .highlight::after {
            content: '';
            position: absolute;
            bottom: 0;
            left: 0;
            width: 100%;
            height: 30%;
            background-color: rgba(59, 130, 246, 0.3);
            z-index: -1;
            transform: scaleX(0);
            transform-origin: left;
            transition: transform 0.3s ease;
        }
        .highlight:hover::after {
            transform: scaleX(1);
        }
    </style>
</head>
<body class="min-h-screen">
    <!-- Hero Section -->
    <section class="hero-gradient text-white py-20 px-6 md:py-32">
        <div class="max-w-5xl mx-auto text-center">
            <div class="inline-block px-4 py-2 bg-white bg-opacity-20 rounded-full mb-6">
                <span class="text-sm font-medium">动态规划专题</span>
            </div>
            <h1 class="text-4xl md:text-6xl font-bold mb-6 font-serif">零钱兑换问题</h1>
            <p class="text-xl md:text-2xl max-w-3xl mx-auto leading-relaxed opacity-90">
                探索如何用最少数量的硬币组合出给定金额的高效算法
            </p>
            <div class="mt-10 flex justify-center">
                <div class="animate-bounce text-2xl">
                    <i class="fas fa-chevron-down"></i>
                </div>
            </div>
        </div>
    </section>

    <!-- Main Content -->
    <main class="max-w-6xl mx-auto px-6 py-16">
        <!-- Problem Statement -->
        <section class="mb-20">
            <h2 class="text-3xl font-bold mb-6 font-serif relative highlight inline-block">题目描述</h2>
            <div class="bg-white rounded-xl shadow-md p-8">
                <p class="text-lg leading-relaxed mb-6">
                    给定不同面额的硬币 <span class="font-mono bg-gray-100 px-2 py-1 rounded">coins</span> 和一个总金额 <span class="font-mono bg-gray-100 px-2 py-1 rounded">amount</span>。编写一个函数来计算可以凑成总金额所需的最少的硬币个数。如果没有任何一种硬币组合能组成总金额，返回 <span class="font-mono bg-gray-100 px-2 py-1 rounded">-1</span>。
                </p>
                <div class="bg-blue-50 border-l-4 border-blue-500 p-4 rounded-r-lg mb-6">
                    <div class="flex items-start">
                        <div class="flex-shrink-0 mt-1">
                            <i class="fas fa-info-circle text-blue-500"></i>
                        </div>
                        <div class="ml-3">
                            <p class="text-blue-700 font-medium">示例</p>
                            <p class="text-blue-600">
                                输入：coins = [1, 2, 5], amount = 11 <br>
                                输出：3 <br>
                                解释：11 = 5 + 5 + 1
                            </p>
                        </div>
                    </div>
                </div>
                <div class="flex items-center text-gray-500">
                    <i class="fas fa-lightbulb mr-2"></i>
                    <span>这个问题是经典的动态规划问题，常用于算法面试和编程竞赛</span>
                </div>
            </div>
        </section>

        <!-- Core Algorithm -->
        <section class="mb-20">
            <h2 class="text-3xl font-bold mb-6 font-serif relative highlight inline-block">核心算法</h2>
            <div class="grid md:grid-cols-2 gap-8">
                <div class="bg-white rounded-xl shadow-md p-8">
                    <h3 class="text-xl font-bold mb-4 text-indigo-600 flex items-center">
                        <i class="fas fa-project-diagram mr-2"></i>
                        动态规划思路
                    </h3>
                    <p class="mb-4">定义 <span class="font-mono bg-gray-100 px-2 py-1 rounded">dp[i]</span> 为组成金额 <span class="font-mono bg-gray-100 px-2 py-1 rounded">i</span> 所需的最少硬币数量：</p>
                    <ul class="space-y-3 mb-6">
                        <li class="flex items-start">
                            <span class="bg-indigo-100 text-indigo-600 rounded-full w-6 h-6 flex items-center justify-center mr-3 flex-shrink-0">1</span>
                            <span>初始值设为较大的数 (amount + 1)</span>
                        </li>
                        <li class="flex items-start">
                            <span class="bg-indigo-100 text-indigo-600 rounded-full w-6 h-6 flex items-center justify-center mr-3 flex-shrink-0">2</span>
                            <span>状态转移方程：<span class="font-mono bg-gray-100 px-2 py-1 rounded">dp[i] = min(dp[i], dp[i-coin] + 1)</span></span>
                        </li>
                        <li class="flex items-start">
                            <span class="bg-indigo-100 text-indigo-600 rounded-full w-6 h-6 flex items-center justify-center mr-3 flex-shrink-0">3</span>
                            <span>时间复杂度：O(n*m)，空间复杂度：O(n)</span>
                        </li>
                    </ul>
                    
                    <div class="mermaid mt-6">
                        graph TD
                            A[开始] --> B[初始化dp数组]
                            B --> C[遍历每种硬币]
                            C --> D[对于当前硬币,计算每个金额的最少硬币数]
                            D --> E[更新dp数组]
                            E --> F{所有硬币处理完成?}
                            F -->|否| C
                            F -->|是| G[返回结果]
                    </div>
                </div>
                
                <div class="bg-white rounded-xl shadow-md overflow-hidden">
                    <div class="p-8">
                        <h3 class="text-xl font-bold mb-4 text-indigo-600 flex items-center">
                            <i class="fas fa-code mr-2"></i>
                            算法实现
                        </h3>
                        <div class="code-block">
                            <div class="flex items-center justify-between bg-gray-800 px-4 py-2">
                                <div class="flex space-x-2">
                                    <span class="w-3 h-3 bg-red-500 rounded-full"></span>
                                    <span class="w-3 h-3 bg-yellow-500 rounded-full"></span>
                                    <span class="w-3 h-3 bg-green-500 rounded-full"></span>
                                </div>
                                <span class="text-gray-400 text-sm">Java 实现</span>
                            </div>
                            <pre class="p-4 text-gray-200 overflow-auto"><code class="language-java">public int coinChange(int[] coins, int amount) {
    // 定义一个较大的值作为初始值
    int MAX = amount + 1;
    
    // 创建动态规划数组，dp[i]表示组成金额i所需的最少硬币数
    int[] dp = new int[amount + 1];
    
    // 初始化dp数组，所有位置设为最大值
    Arrays.fill(dp, MAX);
    
    // 组成金额0需要0个硬币
    dp[0] = 0;
    
    // 遍历每种硬币
    for (int coin : coins) {
        // 对于当前硬币，计算从coin到amount的每个金额所需的最少硬币数
        for (int i = coin; i <= amount; i++) {
            // 当前金额i的最少硬币数 = min(当前值, 金额(i-coin)的最少硬币数+1枚当前硬币)
            dp[i] = Math.min(dp[i], dp[i - coin] + 1);
        }
    }
    
    // 如果最终结果仍是初始的MAX值，说明无法组成该金额，返回-1
    return dp[amount] < MAX ? dp[amount] : -1;
}</code></pre>
                        </div>
                    </div>
                    <div class="bg-gray-50 px-8 py-4 border-t border-gray-200">
                        <div class="flex items-center text-gray-600">
                            <i class="fas fa-clock mr-2"></i>
                            <span>关键点：初始化、状态转移、边界条件</span>
                        </div>
                    </div>
                </div>
            </div>
        </section>

        <!-- Visualization -->
        <section class="mb-20">
            <h2 class="text-3xl font-bold mb-6 font-serif relative highlight inline-block">动态规划过程可视化</h2>
            <div class="bg-white rounded-xl shadow-md p-8">
                <div class="mb-8">
                    <h3 class="text-xl font-bold mb-4 text-indigo-600">示例演示：coins = [1, 2, 5], amount = 11</h3>
                    <p class="text-gray-600 mb-4">下面展示了动态规划数组的逐步填充过程：</p>
                    
                    <div class="overflow-x-auto">
                        <div class="inline-block min-w-full">
                            <div class="grid grid-cols-13 gap-2 mb-4">
                                <div class="text-center font-medium">金额</div>
                                <div class="text-center">0</div>
                                <div class="text-center">1</div>
                                <div class="text-center">2</div>
                                <div class="text-center">3</div>
                                <div class="text-center">4</div>
                                <div class="text-center">5</div>
                                <div class="text-center">6</div>
                                <div class="text-center">7</div>
                                <div class="text-center">8</div>
                                <div class="text-center">9</div>
                                <div class="text-center">10</div>
                                <div class="text-center">11</div>
                            </div>
                            
                            <!-- Initialization -->
                            <div class="grid grid-cols-13 gap-2 mb-2">
                                <div class="font-medium">初始化</div>
                                <div class="dp-cell bg-blue-100 text-blue-800 p-2 rounded text-center">0</div>
                                <div class="dp-cell bg-gray-200 text-gray-700 p-2 rounded text-center">12</div>
                                <div class="dp-cell bg-gray-200 text-gray-700 p-2 rounded text-center">12</div>
                                <div class="dp-cell bg-gray-200 text-gray-700 p-2 rounded text-center">12</div>
                                <div class="dp-cell bg-gray-200 text-gray-700 p-2 rounded text-center">12</div>
                                <div class="dp-cell bg-gray-200 text-gray-700 p-2 rounded text-center">12</div>
                                <div class="dp-cell bg-gray-200 text-gray-700 p-2 rounded text-center">12</div>
                                <div class="dp-cell bg-gray-200 text-gray-700 p-2 rounded text-center">12</div>
                                <div class="dp-cell bg-gray-200 text-gray-700 p-2 rounded text-center">12</div>
                                <div class="dp-cell bg-gray-200 text-gray-700 p-2 rounded text-center">12</div>
                                <div class="dp-cell bg-gray-200 text-gray-700 p-2 rounded text-center">12</div>
                                <div class="dp-cell bg-gray-200 text-gray-700 p-2 rounded text-center">12</div>
                            </div>
                            
                            <!-- Coin 1 -->
                            <div class="grid grid-cols-13 gap-2 mb-2">
                                <div class="font-medium">硬币1</div>
                                <div class="dp-cell bg-blue-100 text-blue-800 p-2 rounded text-center">0</div>
                                <div class="dp-cell bg-green-100 text-green-800 p-2 rounded text-center">1</div>
                                <div class="dp-cell bg-green-100 text-green-800 p-2 rounded text-center">2</div>
                                <div class="dp-cell bg-green-100 text-green-800 p-2 rounded text-center">3</div>
                                <div class="dp-cell bg-green-100 text-green-800 p-2 rounded text-center">4</div>
                                <div class="dp-cell bg-green-100 text-green-800 p-2 rounded text-center">5</div>
                                <div class="dp-cell bg-green-100 text-green-800 p-2 rounded text-center">6</div>
                                <div class="dp-cell bg-green-100 text-green-800 p-2 rounded text-center">7</div>
                                <div class="dp-cell bg-green-100 text-green-800 p-2 rounded text-center">8</div>
                                <div class="dp-cell bg-green-100 text-green-800 p-2 rounded text-center">9</div>
                                <div class="dp-cell bg-green-100 text-green-800 p-2 rounded text-center">10</div>
                                <div class="dp-cell bg-green-100 text-green-800 p-2 rounded text-center">11</div>
                            </div>
                            
                            <!-- Coin 2 -->
                            <div class="grid grid-cols-13 gap-2 mb-2">
                                <div class="font-medium">硬币2</div>
                                <div class="dp-cell bg-blue-100 text-blue-800 p-2 rounded text-center">0</div>
                                <div class="dp-cell bg-green-100 text-green-800 p-2 rounded text-center">1</div>
                                <div class="dp-cell bg-yellow-100 text-yellow-800 p-2 rounded text-center">1</div>
                                <div class="dp-cell bg-yellow-100 text-yellow-800 p-2 rounded text-center">2</div>
                                <div class="dp-cell bg-yellow-100 text-yellow-800 p-2 rounded text-center">2</div>
                                <div class="dp-cell bg-yellow-100 text-yellow-800 p-2 rounded text-center">3</div>
                                <div class="dp-cell bg-yellow-100 text-yellow-800 p-2 rounded text-center">3</div>
                                <div class="dp-cell bg-yellow-100 text-yellow-800 p-2 rounded text-center">4</div>
                                <div class="dp-cell bg-yellow-100 text-yellow-800 p-2 rounded text-center">4</div>
                                <div class="dp-cell bg-yellow-100 text-yellow-800 p-2 rounded text-center">5</div>
                                <div class="dp-cell bg-yellow-100 text-yellow-800 p-2 rounded text-center">5</div>
                                <div class="dp-cell bg-yellow-100 text-yellow-800 p-2 rounded text-center">6</div>
                            </div>
                            
                            <!-- Coin 5 -->
                            <div class="grid grid-cols-13 gap-2">
                                <div class="font-medium">硬币5</div>
                                <div class="dp-cell bg-blue-100 text-blue-800 p-2 rounded text-center">0</div>
                                <div class="dp-cell bg-green-100 text-green-800 p-2 rounded text-center">1</div>
                                <div class="dp-cell bg-yellow-100 text-yellow-800 p-2 rounded text-center">1</div>
                                <div class="dp-cell bg-yellow-100 text-yellow-800 p-2 rounded text-center">2</div>
                                <div class="dp-cell bg-yellow-100 text-yellow-800 p-2 rounded text-center">2</div>
                                <div class="dp-cell bg-purple-100 text-purple-800 p-2 rounded text-center">1</div>
                                <div class="dp-cell bg-purple-100 text-purple-800 p-2 rounded text-center">2</div>
                                <div class="dp-cell bg-purple-100 text-purple-800 p-2 rounded text-center">2</div>
                                <div class="dp-cell bg-purple-100 text-purple-800 p-2 rounded text-center">3</div>
                                <div class="dp-cell bg-purple-100 text-purple-800 p-2 rounded text-center">3</div>
                                <div class="dp-cell bg-purple-100 text-purple-800 p-2 rounded text-center">2</div>
                                <div class="dp-cell bg-purple-100 text-purple-800 p-2 rounded text-center">3</div>
                            </div>
                        </div>
                    </div>
                    
                    <div class="mt-6 p-4 bg-indigo-50 rounded-lg">
                        <div class="flex items-start">
                            <div class="flex-shrink-0 mt-1">
                                <i class="fas fa-check-circle text-indigo-500"></i>
                            </div>
                            <div class="ml-3">
                                <p class="text-indigo-700 font-medium">最终结果</p>
                                <p class="text-indigo-600">
                                    对于金额11，最少需要3个硬币（5 + 5 + 1）
                                </p>
                            </div>
                        </div>
                    </div>
                </div>
                
                <div class="mermaid">
                    gantt
                        title 动态规划过程时间线
                        dateFormat  X
                        axisFormat %s
        
                        section 初始化
                        dp数组初始化 : 0, 1s
        
                        section 处理硬币1
                        更新dp[1-11] : 1, 2s
        
                        section 处理硬币2
                        更新dp[2-11] : 2, 3s
        
                        section 处理硬币5
                        更新dp[5-11] : 3, 4s
                </div>
            </div>
        </section>

        <!-- Key Concepts -->
        <section>
            <h2 class="text-3xl font-bold mb-6 font-serif relative highlight inline-block">核心概念解析</h2>
            <div class="grid md:grid-cols-3 gap-6">
                <div class="concept-card bg-white p-6 rounded-lg shadow-sm">
                    <div class="text-blue-500 text-2xl mb-3">
                        <i class="fas fa-sitemap"></i>
                    </div>
                    <h3 class="text-xl font-bold mb-3">动态规划</h3>
                    <p class="text-gray-600">
                        通过分解问题为子问题，存储并重用子问题的解来优化性能。零钱兑换问题中，dp[i]存储金额i的最优解。
                    </p>
                </div>
                
                <div class="concept-card bg-white p-6 rounded-lg shadow-sm">
                    <div class="text-green-500 text-2xl mb-3">
                        <i class="fas fa-exchange-alt"></i>
                    </div>
                    <h3 class="text-xl font-bold mb-3">状态转移</h3>
                    <p class="text-gray-600">
                        dp[i] = min(dp[i], dp[i-coin]+1)是关键转移方程，表示当前金额的最优解可以通过较小的金额加上一枚硬币得到。
                    </p>
                </div>
                
                <div class="concept-card bg-white p-6 rounded-lg shadow-sm">
                    <div class="text-purple-500 text-2xl mb-3">
                        <i class="fas fa-flask"></i>
                    </div>
                    <h3 class="text-xl font-bold mb-3">边界条件</h3>
                    <p class="text-gray-600">
                        初始化dp[0]=0是基础条件，表示金额0需要0个硬币。数组其他位置初始化为大数，便于后续比较。
                    </p>
                </div>
            </div>
        </section>
    </main>

    <script>
        mermaid.initialize({
            startOnLoad: true,
            theme: 'default',
            flowchart: {
                useMaxWidth: false,
                htmlLabels: true,
                curve: 'basis'
            },
            gantt: {
                barHeight: 20,
                fontSize: 12
            }
        });
        
        // 微交互效果
        document.querySelectorAll('.dp-cell').forEach(cell => {
            cell.addEventListener('mouseenter', function() {
                const amount = this.textContent;
                if (amount !== '0' && amount !== '初始化' && !isNaN(amount)) {
                    this.title = `最少需要 ${amount} 枚硬币`;
                }
            });
        });
    </script>
</body>
</html>
```